package com.ayg.insurance.dao.impl;

import java.io.Serializable;
import java.lang.reflect.ParameterizedType;

import javax.annotation.Resource;

import org.springframework.dao.DataAccessException;
import org.springframework.data.redis.connection.RedisConnection;
import org.springframework.data.redis.core.RedisCallback;
import org.springframework.data.redis.core.RedisTemplate;

import com.ayg.insurance.utils.SerializeUtil;

public abstract class RedisDao<K extends Serializable, T extends Serializable> {
	
	protected @Resource RedisTemplate<K, T> redisTemplate;
    
	/**
	 * 	保存redis
	 * @param key key值
	 * @param value 要保存的对象
	 * @param timeout 缓存存活时间
	 */
	public void setRedis(final K key, final T value, final long timeout) {
		redisTemplate.execute(new RedisCallback<Boolean>() {
			@Override
			public Boolean doInRedis(RedisConnection connection)throws DataAccessException {
				connection.setEx(SerializeUtil.serialize(key) , timeout, SerializeUtil.serialize(value));
				return true;
			}
		});
//		redisTemplate.opsForHash().put(key, value.getClass().getName(), value);
//		redisTemplate.expire(key, timeout, TimeUnit.SECONDS);
	}
	
	/**
	 *  读取redis
	 * @param key
	 * @return
	 */
	@SuppressWarnings("unchecked")
	public T getRedis(final K key){
		return redisTemplate.execute(new RedisCallback<T>() {
			@Override
			public T doInRedis(RedisConnection connection)throws DataAccessException {
				byte[] bytes = connection.get(SerializeUtil.serialize(key));
				if(bytes!=null){
					return (T) SerializeUtil.unserialize(bytes);
				}
				return null;
			}
		});
//		return (T) redisTemplate.opsForHash().get(key, genericClass().getName());  
    }
	
	
	/**
	 * 返回当前泛型对应的类型
	 * @return
	 */
	@SuppressWarnings("unchecked")
	protected Class<T> genericClass() {
		Class<T> entityClass = (Class<T>) ((ParameterizedType) getClass()
				.getGenericSuperclass()).getActualTypeArguments()[1];
		if (entityClass == null) {
			throw new UnsupportedOperationException("Can not get generic class type");
		}
		return entityClass;
	}
	
}
